/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package repositoriodistribuido;

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.rmi.RemoteException;
import java.util.Vector;
import java.util.logging.Level;
import java.util.logging.Logger;
import nanoxml.XMLElement;

/**
 *
 * @author ylopez
 */
public class dcliCommands {

    private static String currentDirectory;

    public static void setCurrentDirectory(String currentDirectory){
        dcliCommands.currentDirectory = currentDirectory;
    }

    public static String[] ldir(String path){
        File dir = new File(path);
        File[] ficheros = dir.listFiles();
        int i = 0;
        String[] archivos = null;

        if(ficheros==null){
            System.out.println("No hay ficheros en el directorio especificado \n"+path);
        }else {
            archivos = new String[2*ficheros.length];
            while(i<ficheros.length){
                archivos[2*i] = ficheros[i].getName();
                archivos[2*i+1] = Long.toString(ficheros[i].length());
                i++;
            }
        }
        return archivos;
    }

    /**Crea una copia del archivo con nombre file del cliente en el directorio
 * dir del servidor
 *
 * @param file nombre del archivo a subir
 * @param out mensaje de solicitud del cliente al servidor
 * @param in mensaje de entrada recibido desde el protocolo
 * @param dir directorio donde se debe colocar la copia del archivo
 * @return content contenido del archivo a subir
 */
    public static String[] sube(String fileName, drepCommands c) throws RemoteException{
        String[] result = null;
        try {
            File file = new File(currentDirectory+"/"+fileName);
            if (file.exists()){
                byte buffer[] = new byte[(int)file.length()];
                BufferedInputStream input = new BufferedInputStream(new FileInputStream(file));
                input.read(buffer,0,buffer.length);
                input.close();
                result = new String[]{c.sendFile(fileName, buffer)};
            } else {
                result = new String[]{"Archivo no existe"};
            }
        } catch(Exception e){
            System.out.println("FileImpl: "+e.getMessage());
            e.printStackTrace();
            return(null);
        }
        return result;
    }

    public static String[] baja(String fileName, drepCommands c) throws RemoteException{
        String[] result = null;
        if(c.existFile(fileName)){
            try {
                byte[] filedata = c.downloadFile(fileName);
                FileOutputStream fos = new FileOutputStream(currentDirectory+"/"+fileName);
                BufferedOutputStream output = new BufferedOutputStream(fos);
                output.write(filedata,0,filedata.length);
                output.flush();
                output.close();
                result = new String[]{"OK"};
            } catch(Exception e) {
                System.err.println("Error en baja: "+ e.getMessage());
                e.printStackTrace();
            }
        } else {
            result = new String[]{"Archivo no existe"};
        }

        return result;

    }

    public static void cat(String file){
        try {
            FileReader fr;
            BufferedReader bf;
            String line = "";

            fr = new FileReader(file);
            bf = new BufferedReader(fr);
            System.out.println("Inicio ejecuci'on cat:");
            while ((line = bf.readLine())!=null) {
                System.out.print(line+"\n");
            }
            System.out.println("Final ejecuci'on cat");

        } catch (IOException ex) {
            ex.printStackTrace();
        }
    }

    public static void readCommandsFromFile(String file, drepCommands c){
        try {
            FileReader fr;
            BufferedReader bf;
            String line = "";
            String[] command;
            String[] results;

            fr = new FileReader(file);
            bf = new BufferedReader(fr);
            
            while ((line = bf.readLine())!=null) {
                command = line.split(" ");
                if (command[0].equals("ldir")) {
                    results = ldir(currentDirectory);
                    printResoults("ldir", results);
                } else if (command[0].equals("rdir")) {
                    results = c.rdir();
                    printResoults("rdir", results);
                } else if (command[0].equals("tuser")) {
                    results = c.tuser();
                    printResoults("tuser", results);
                } else if (command[0].equals("nrep")) {
                    results = c.nrep();
                    printResoults("nrep", results);
                } else if (command[0].equals("sube")) {
                    results = dcliCommands.sube(command[1],c);
                    dcliCommands.printResoults("sube", results);
                } else if (command[0].equals("baja")) {
                    results = dcliCommands.baja(command[1],c);
                    dcliCommands.printResoults("baja", results);
                } else if (command[0].equals("cat")) {
                    cat(command[1]);
                } else {
                    System.err.println("Comando: "+ command[0] +" invalido.");
                }
            }

            bf.close();
            fr.close();

        } catch (IOException ex) {
            String [] exceptionMessage = ex.getMessage().split(" ");
            String permissionDeniedMessage = exceptionMessage[1] + " " + exceptionMessage[2];
            if(permissionDeniedMessage.equals("(Permission denied)")){
                System.err.println("No tiene permiso de lectura para: " + exceptionMessage[0]);
            } else {
                ex.printStackTrace();
                System.exit(-1);
            }
        }
    }

    public static void printResoults(String flag, String[] resoults){
        System.out.println("Inicio ejecuci'on "+ flag +":");
        if (flag.equals("ldir") || flag.equals("rdir") || flag.equals("tuser")) {
            for (int i = 0; i < resoults.length; i += 2) {
                System.out.println(resoults[i] + " " + resoults[i+1]);
            }
        }
        if (flag.equals("nrep")) {
            System.out.println("N'umero de repositorios: " + resoults[0]);
        }

        if (flag.equals("sube") || flag.equals("baja")) {
            System.out.println("Estatus de "+ flag +": " + resoults[0]);
        }
        System.out.println("Final ejecuci'on "+ flag +".");
    }

    public static String[] getParameter(String file) throws FileNotFoundException, IOException{
        String[] valuesForParameter;
        XMLElement xml = new XMLElement();
        FileReader reader = new FileReader(file);
        xml.parseFromReader(reader);
        Vector<XMLElement> parameters = xml.getChildren();

        valuesForParameter = new String[parameters.size()];
        valuesForParameter[0] = "vacio";
        valuesForParameter[1] = "vacio";
        valuesForParameter[2] = "vacio";
        valuesForParameter[3] = "vacio";
        valuesForParameter[4] = "vacio";

        for (XMLElement parameter : parameters) {
            if (parameter.getName().equals("nombre")) {
                valuesForParameter[0] = parameter.getContent();
            }
            if (parameter.getName().equals("hostserv")) {
                valuesForParameter[1] = parameter.getContent();
            }
            if (parameter.getName().equals("puertoserv")) {
                valuesForParameter[2] = parameter.getContent();
            }
            if (parameter.getName().equals("directorio")) {
                valuesForParameter[3] = parameter.getContent();
            }
            if (parameter.getName().equals("archivo")) {
                valuesForParameter[4] = parameter.getContent();
            }
        }

        return valuesForParameter;
    }
}
